package webgamemaker.Editor;

import java.util.ArrayList;

import webgamemaker.Common.MapData;
import webgamemaker.Common.TileSet;

import com.smartgwt.client.widgets.grid.events.CellContextClickEvent;
import com.smartgwt.client.widgets.grid.events.CellContextClickHandler;
import com.smartgwt.client.widgets.grid.events.CellDoubleClickEvent;
import com.smartgwt.client.widgets.grid.events.CellDoubleClickHandler;
import com.smartgwt.client.widgets.menu.Menu;
import com.smartgwt.client.widgets.menu.MenuItem;
import com.smartgwt.client.widgets.menu.events.ClickHandler;
import com.smartgwt.client.widgets.menu.events.MenuItemClickEvent;
import com.smartgwt.client.widgets.tree.Tree;
import com.smartgwt.client.widgets.tree.TreeGrid;
import com.smartgwt.client.widgets.tree.TreeGridField;
import com.smartgwt.client.widgets.tree.TreeNode;

public class ProjectTree extends TreeGrid 
{
	public Tree tree;
	public TreeNode rootNode;
	public ArrayList<MapTreeNode> mapNode;
	public Menu mainTilesetContextMenu, subTilesetContextMenu;
	public MenuItem addTileSetItem, editTileSetItem, removeTileSetItem;
	public TreeNode selectedNode;
	
	public ProjectTree()
	{
		setShowConnectors(true);
		setFields(new TreeGridField("Name"));
		
		tree = new Tree();
		rootNode = new TreeNode();
		tree.setRoot(rootNode);
		
		mapNode = new ArrayList<MapTreeNode>();
		
		mainTilesetContextMenu = new Menu();
		addTileSetItem = new MenuItem("add tileset");
		addTileSetItem.addClickHandler(new ClickHandler()
			{
				public void onClick(MenuItemClickEvent event) 
				{
					if(selectedNode instanceof TileSetTreeNode)
					new AddTileSetWindow(((TileSetTreeNode)selectedNode).father.mapData).show();
				}
			});
		mainTilesetContextMenu.addItem(addTileSetItem);
		
		subTilesetContextMenu = new Menu();
		editTileSetItem = new MenuItem("edit tileset");
		editTileSetItem.addClickHandler(new ClickHandler()
			{
				public void onClick(MenuItemClickEvent event) 
				{
					if(selectedNode instanceof TileSetTreeNode)
						ProjectManager.getInstance().editTileSet(((TileSetTreeNode)selectedNode).tileset);
				}
			});
		subTilesetContextMenu.addItem(editTileSetItem);
		removeTileSetItem = new MenuItem("remove tileset");
		removeTileSetItem.addClickHandler(new ClickHandler()
			{
				public void onClick(MenuItemClickEvent event) 
				{
					if(selectedNode instanceof TileSetTreeNode)
					;//new AddTileSetWindow(((TileSetTreeNode)selectedNode).father.mapData).show();
				}
			});
		subTilesetContextMenu.addItem(removeTileSetItem);
		
		addCellContextClickHandler(new CellContextClickHandler()
		{
			public void onCellContextClick(CellContextClickEvent event) 
			{
				selectedNode = (TreeNode) event.getRecord();
				if(selectedNode instanceof TileSetTreeNode)
					((TileSetTreeNode)selectedNode).onContextMenu();
				else event.cancel();
			}
		
		});
		
		this.addCellDoubleClickHandler(new CellDoubleClickHandler()
			{
				public void onCellDoubleClick(CellDoubleClickEvent event) 
				{
					selectedNode = (TreeNode) event.getRecord();
					if(selectedNode instanceof MapTreeNode)
						((MapTreeNode)selectedNode).onDoubleClick();
					else if(selectedNode instanceof TileSetTreeNode)
						((TileSetTreeNode)selectedNode).onDoubleClick();
				}
			});
		
		setData(tree);
	}
	
	public MapTreeNode findTreeNode(MapData data)
	{
		for(MapTreeNode node : mapNode)
			if(node.mapData == data)
				return node;
		return null;
	}
	
	public MapTreeNode addMap(MapData data)
	{
		MapTreeNode node = new MapTreeNode(rootNode, data);
		mapNode.add(node);
		for(TileSet tileset : data.listTileSet)
			node.addTileSet(tileset);
		return node;
	}
	
	public TileSetTreeNode addTileSet(MapData data, TileSet tileset)
	{
		MapTreeNode node = findTreeNode(data);
		if(node == null)
			node = addMap(data);
		return node.addTileSet(tileset);
	}
	
	public void removeTileSet(MapData data, TileSet tileset)
	{
		MapTreeNode node = findTreeNode(data);
		if(node != null)
		{
			node.removeTileSet(tileset);
		}
	}
	
	class MapTreeNode extends TreeNode
	{
		public MapData mapData;
		public TileSetTreeNode rootTilesetNode;
		public ArrayList<TileSetTreeNode> tilesetNode;
		
		public MapTreeNode(TreeNode father, MapData data)
		{
			this.mapData = data;
			setAttribute("Name", data.name);
			tree.add(this, father);
			rootTilesetNode = new TileSetTreeNode(this, null);
			tilesetNode = new ArrayList<TileSetTreeNode>();
		}
		
		public TileSetTreeNode find(TileSet tileset)
		{
			for(TileSetTreeNode node : tilesetNode)
				if(node.tileset == tileset)
					return node;
			return null;
		}
		
		public TileSetTreeNode addTileSet(TileSet tileset)
		{
			TileSetTreeNode node = new TileSetTreeNode(this, tileset);
			tilesetNode.add(node);
			return node;
		}
		
		public void removeTileSet(TileSet tileset)
		{
			TileSetTreeNode node = find(tileset);
			if(node != null)
			{
				tree.remove(node);
				tilesetNode.remove(node);
			}
		}
		
		public void onDoubleClick()
		{
			ProjectManager.getInstance().selectMap(mapData);
		}
	}
	
	class TileSetTreeNode extends TreeNode
	{
		public MapTreeNode father;
		public TileSet tileset;
		
		public TileSetTreeNode(MapTreeNode father, TileSet tileset)
		{
			this.father = father;
			if(tileset != null)
			{
				this.tileset = tileset;
				setAttribute("Name", tileset.name);
				tree.add(this, father.rootTilesetNode);
			}
			else 
			{
				setAttribute("Name", "tileset");
				tree.add(this, father);
			}
		}
		
		public void onContextMenu()
		{
			if(tileset == null)
				setContextMenu(mainTilesetContextMenu);
			else setContextMenu(subTilesetContextMenu);
		}
		
		public void onDoubleClick()
		{
			if(tileset != null)
				ProjectManager.getInstance().selectTileSet(father.mapData, tileset);
		}
	}
}
